<?php

class PDOMySQL
{
    public static $dbtype = 'mysqli';//Environment::DBTYPE;
    public static $dbhost = 'db.test.freshqiao.com';//Environment::DBHOST;
    public static $dbport = '3306';//Environment::DBPORT;
    public static $dbname = 'test';//Environment::DBNAME;
    public static $dbuser = 'rrcc';//Environment::DBUSER;
    public static $dbpass = 'renrenc@ich@ng';//Environment::DBPASS;
    public static $charset = 'utf8';//Environment::CHARSET;
    public static $timeout = 10;
    public static $stmt = null;
    public static $connect = false; // 长链接是否开启
    private static $DB = null;

    public function __construct()
    {
        try {
            if (self::$DB == null) {
                self::$DB = new PDO(self::$dbtype . ':host=' . self::$dbhost . ';port=' . self::$dbport . ';dbname=' . self::$dbname, self::$dbuser, self::$dbpass, array(
                    PDO::ATTR_PERSISTENT => self::$connect,
                    PDO::ATTR_TIMEOUT => self::$timeout
                ));
            }
        } catch (PDOException $e) {
            die("Connect Error Information:" . $e->getMessage());
        }
        self::$DB->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, true);
        self::$DB->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);
        self::execute('SET NAMES ' . self::$charset);
    }

    public function execute($sql)
    {
        return self::$DB->exec($sql);
    }

    public function query($sql)
    {
        self::$stmt = self::$DB->query($sql);
        self::$stmt->setFetchMode(PDO::FETCH_ASSOC);
        return self::$stmt->fetchAll();
    }

    public function getLastId()
    {
        return self::$DB->lastInsertId();
    }

    public function insert($table, $args)
    {
        if (empty($args)) {
            return false;
        }
        $sql = "INSERT INTO `$table` SET ";
        $code = self::_getCode($args);
        $sql .= $code;
        $result = self::execute($sql);
        if (self::$DB->errorCode() != '00000') {
            $err_info = self::$DB->errorInfo();
            throw new Exception("SQL error: $sql" . '. Error info: ' . isset($err_info[2]) ? $err_info[2] : '');
        }
        return $result;
    }

    private function _getCode($args)
    {
        $code = '';
        if (is_array($args)) {
            foreach ($args as $k => $v) {
                $code .= "`$k`='$v',";
            }
        }
        $code = substr($code, 0, -1);
        return $code;
    }

    public function update($table, $args, $where)
    {
        if (empty($where)) {
            return false;
        }
        $code = self::_getCode($args);
        $sql = "UPDATE `$table` SET ";
        $sql .= $code;
        $sql .= " WHERE $where";
        $result = self::execute($sql);
        if (self::$DB->errorCode() != '00000') {
            $err_info = self::$DB->errorInfo();
            throw new Exception("SQL error: $sql" . '. Error info: ' . isset($err_info[2]) ? $err_info[2] : '');
        }
        return $result;
    }

    public function delete($table, $where)
    {
        if (empty($where)) return false;
        $sql = "DELETE FROM `$table` Where $where";
        return self::execute($sql);
    }

    public function fetchOne($table, $field = '*', $where = false)
    {
        $sql = "SELECT {$field} FROM `{$table}`";
        $sql .= $where ? " WHERE $where" : '';
        return self::_fetch($sql, $type = '0');
    }

    public function _fetch($sql, $type)
    {
        $result = array();
        self::$stmt = self::$DB->query($sql);
        if (self::$stmt == false) {
            $err_info = self::$DB->errorInfo();
            throw new Exception("SQL error: $sql" . '. Error info: ' . isset($err_info[2]) ? $err_info[2] : '');
        }

        self::$stmt->setFetchMode(PDO::FETCH_ASSOC);
        switch ($type) {
            case '0':
                $result = self::$stmt->fetch();
                break;
            case '1':
                $result = self::$stmt->fetchAll();
                break;

        }
        self::$stmt = null;
        return $result;
    }

    public function fetchAll($table, $field = '*', $orderby = false, $where = false, $limit = false, $offset = 0)
    {
        $sql = "SELECT {$field} FROM `{$table}`";
        $sql .= $where ? " WHERE $where" : '';
        $sql .= $orderby ? " ORDER BY $orderby" : '';
        $sql .= $limit ? " LIMIT  $offset, $limit" : '';
        return self::_fetch($sql, $type = '1');
    }

    public function fetchRowCount($table, $field = '*', $where = false)
    {
        $sql = "SELECT COUNT({$field}) AS num FROM $table";
        $sql .= $where ? " WHERE $where" : '';
        return self::_fetch($sql, $type = '0');
    }

    public function beginTransaction()
    {
        return self::$DB->beginTransaction();
    }

    public function commit()
    {
        return self::$DB->commit();
    }

    public function rollBack()
    {
        return self::$DB->rollBack();
    }

    //添加写sql 的方法
    public function actSql($sql)
    {
        return self::_fetch($sql, $type = '1');
    }

    //添加 调用 储存过程的方法
    public function call_post($callString)
    {
        return self::$DB->prepare($callString);
    }
}